package kiwi.assist.dev.guieditor.command {
	import flash.system.ApplicationDomain;
	import flash.system.LoaderContext;

	import fl.managers.StyleManager;

	import ghostcat.fileformat.swf.SWFDecoder;
	import ghostcat.fileformat.swf.tag.SymbolClassTag;
	import ghostcat.util.ReflectUtil;
	import ghostcat.util.core.ClassFactory;

	import kiwi.assist.dev.guieditor.event.GUIEditorEvent;
	import kiwi.assist.dev.guieditor.model.GUIEditorConfig;
	import kiwi.assist.dev.guieditor.model.SkinConfig;
	import kiwi.assist.dev.guieditor.model.StyleLibConfig;
	import kiwi.assist.dev.guieditor.model.UiConfig;
	import kiwi.assist.dev.reflect.FlashUiComponentReflectFactoryImpl;
	import kiwi.assist.dev.reflect.IReflectFactory;
	import kiwi.debug.Log;
	import kiwi.util.asserts.assert;

	import com.greensock.events.LoaderEvent;
	import com.greensock.loading.LoaderMax;
	import com.greensock.loading.LoaderStatus;
	import com.greensock.loading.SWFLoader;
	import com.greensock.loading.data.SWFLoaderVars;

	import org.robotlegs.mvcs.Command;

	import flash.display.DisplayObject;
	import flash.events.Event;
	import flash.net.URLLoader;
	import flash.utils.Dictionary;

	/**
	 * gui编辑器的默认样式变更了
	 * @author zhangming.luo
	 */
	public class GuiEditorStyleChangeCommand extends Command {
		[Inject]
		public var event : GUIEditorEvent;
		private var loader : SWFLoader;
		private var style : StyleLibConfig;
		[Inject]
		public var config : GUIEditorConfig;
		private var urlLoader : URLLoader;
		private var decoder : SWFDecoder;

		override public function execute() : void {
			super.execute();
			style = event.data;
			loader = LoaderMax.getLoader(style.src);
			if (loader) {
				if (loader.status == LoaderStatus.COMPLETED) {
					// 加载完毕了
					onComplete(null);
				} else {
					// 其他情况
				}
			} else {
				// 正式加载
				var context : LoaderContext = new LoaderContext(false, ApplicationDomain.currentDomain);
				loader = new SWFLoader(style.src, new SWFLoaderVars().onComplete(onComplete).context(context));
				loader.load();
			}
		}

		private function updateStyle() : void {
			for each (var uiConfig:UiConfig in config.uis) {
				try {
					var factoryClz : Class = uiConfig.factoryClz as Class;
					var factory : IReflectFactory;
					if (factoryClz) {
						factory = injector.instantiate(ReflectUtil.getClass(uiConfig.factoryClz));
					} else {
						factory = injector.instantiate(FlashUiComponentReflectFactoryImpl);
					}
					var uiClz : Class = factory.getClass(uiConfig.defaultConfig);
					assert(uiClz != null, "无法构建目标类型: " + uiConfig.defaultConfig.toXMLString());
					if (uiClz.hasOwnProperty("getStyleDefinition")) {
						var definition : * = uiClz["getStyleDefinition"]();
						for (var key:String in definition) {
							if (!definition[key]) {
								continue;
							}
							var clz : Class = loader.getClass(definition[key]);
							if (clz == null) {
								// 当前的样式库中找不到则使用原来的
								continue;
							}
							// 覆盖原来的设置
							StyleManager.clearComponentStyle(uiClz, key);
							StyleManager.setComponentStyle(uiClz, key, clz);
						}
					} else {
						Log.warn("控件不存在默认样式获取入口: " + uiClz);
					}
				} catch(e : Error) {
					Log.error("注册控件样式错误", e);
				}
			}
			Log.info("样式更新完毕");
		}

		private function onComplete(e : LoaderEvent) : void {
			updateStyle();
			if (!style._raw) {
				// 获取样式列表
				urlLoader = new URLLoader();
				urlLoader.addEventListener(Event.COMPLETE, onSWFLoaded);
				urlLoader.dataFormat = "binary";
				urlLoader.load(loader.request);
			} else {
				decodeSWF();
			}
		}

		private function onSWFLoaded(e : Event) : void {
			urlLoader.removeEventListener(Event.COMPLETE, onSWFLoaded);
			style._raw = urlLoader.data;
			decodeSWF();
		}

		private function decodeSWF() : void {
			if (style.skines) {
				return;
			}
			style.skines = new Dictionary();
			decoder = new SWFDecoder();
			decoder.read(style._raw);
			// 遍历所有的素材
			var tags : Array = decoder.getTags(SymbolClassTag);
			if (tags.length > 0) {
				var classes : Array = tags[0].symbolClasses;
				for each (var className:String in classes) {
					try {
						var clz : Class = loader.getClass(className);
						var skin : * = ClassFactory.apply(clz);
						if (skin is DisplayObject) {
							// 暂时只支持DisplayObject
							var skinConfig : SkinConfig = new SkinConfig(className);
							skinConfig.clz = clz;
							style.skines[className] = skinConfig;
							// 独立注册一部分
							StyleManager.setStyle("#" + className + "#", clz);
						}
					} catch(e : Error) {
						Log.alert("存在不能实例化的样式:" + clz);
					}
				}
			}
			dispatch(new GUIEditorEvent(GUIEditorEvent.STYLE_CHANGE, style));
		}
	}
}
